﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace AntColonyOptimization
{
    internal class Program
    {
        private static void Main(string[] args)
        {
            AntColony colony = new AntColony(100, 100, 0.6F, 4.2F, 0.8F, 3.4F, 22.0F, 1.8F, 1.0F);
            colony.SetTestData(C, D, 26);
            colony.InitializeAlgorithm();
            colony.RunAlgorithm();
            Console.WriteLine(colony.GetMinimalCost());
            /*
            List<int> costs = colony.GetCosts(40);
            foreach (var cost in costs)
            {
                Console.WriteLine(cost);
            }
             */
            Console.ReadKey();
        }

        //26, optimum 5426670, nasz najlepszy 5559145 (bez aktualizacji feromonow, z aktualizacja jakies 50tys wiecej)
        private static int[,] C = {
                                      {
                                          53, 66, 66, 66, 66, 53, 53, 53, 53, 53, 73, 53, 53, 53, 66, 53, 53, 53, 53, 85
                                          ,
                                          73, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 53, 66, 66, 66, 53, 53, 53, 53, 53, 53, 73, 53, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          85, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 53, 66, 66, 53, 53, 53, 53, 53, 53, 53, 73, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 85, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 66, 53, 66, 53, 53, 53, 53, 53, 53, 53, 53, 73, 73, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 85, 85, 53, 53
                                      },
                                      {
                                          66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 53, 53, 53, 53, 73, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 85, 85, 53, 53
                                      },
                                      {
                                          53, 53, 53, 53, 53, 53, 66, 66, 66, 66, 53, 53, 53, 53, 53, 73, 73, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 85, 85
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 53, 66, 66, 66, 53, 53, 53, 53, 53, 73, 73, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 85, 85
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 66, 53, 66, 66, 53, 53, 53, 53, 53, 66, 53, 73, 53, 53
                                          ,
                                          53, 53, 53, 53, 73, 73
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 66, 66, 53, 66, 53, 53, 53, 53, 53, 66, 53, 53, 73, 53
                                          ,
                                          53, 53, 53, 53, 73, 73
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 73, 73
                                      },
                                      {
                                          66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 73, 73, 53, 53
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 53, 66, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 73, 73
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 73, 73
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 73, 73
                                      },
                                      {
                                          53, 53, 53, 53, 53, 66, 66, 66, 66, 66, 53, 53, 53, 53, 53, 66, 53, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 73, 73
                                      },
                                      {
                                          85, 66, 66, 66, 66, 53, 53, 53, 53, 53, 66, 53, 53, 53, 66, 53, 53, 53, 53, 53
                                          ,
                                          73, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 85, 66, 66, 66, 53, 53, 53, 53, 53, 53, 66, 53, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          53, 73, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 85, 66, 66, 53, 53, 53, 53, 53, 53, 53, 66, 53, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 53, 73, 73, 53, 53
                                      },
                                      {
                                          66, 66, 66, 85, 85, 53, 53, 53, 53, 53, 53, 53, 53, 66, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 53, 66, 53, 53
                                      },
                                      {
                                          66, 66, 66, 85, 85, 53, 53, 53, 53, 53, 53, 53, 53, 66, 66, 53, 53, 53, 53, 73
                                          ,
                                          73, 73, 66, 53, 53, 53
                                      },
                                      {
                                          53, 53, 53, 53, 53, 85, 85, 66, 66, 66, 53, 53, 53, 53, 53, 66, 66, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 53, 66
                                      },
                                      {
                                          53, 53, 53, 53, 53, 85, 85, 66, 66, 66, 53, 53, 53, 53, 53, 66, 66, 53, 53, 53
                                          ,
                                          53, 53, 53, 53, 66, 53
                                      }
                                  };

        private static int[,] D = {
                                      {
                                          47, 348, 316, 74, 12, 181, 338, 309, 35, 3, 84, 714, 367, 1153, 7, 71, 0, 687,
                                          432, 507, 975, 38, 6, 8, 7, 15
                                      },
                                      {
                                          175, 9, 0, 4, 1300, 12, 41, 18, 183, 6, 3, 102, 2, 7, 84, 0, 0, 150, 84, 54,
                                          148,
                                          2, 13, 0, 1, 11
                                      },
                                      {
                                          19, 0, 6, 9, 12, 0, 1, 3100, 3, 1, 209, 9, 3, 1, 22, 0, 0, 4, 2, 3, 1, 0, 2, 0
                                          , 0
                                          , 0
                                      },
                                      {
                                          575, 10, 5, 3, 2729, 10, 10, 6, 1186, 0, 4, 48, 46, 30, 103, 11, 0, 102, 36,
                                          34,
                                          160, 2, 14, 0, 3, 1
                                      },
                                      {
                                          56, 265, 165, 249, 45, 142, 391, 398, 2329, 4, 132, 747, 479, 4754, 32, 51, 3,
                                          4501, 1311, 512, 326, 26, 111, 43, 6, 68
                                      },
                                      {
                                          190, 3, 0, 10, 313, 112, 31, 4, 91, 2, 3, 76, 2, 16, 104, 5, 1, 163, 30, 257,
                                          45,
                                          2, 1, 0, 1, 16
                                      },
                                      {
                                          187, 6, 0, 4, 1889, 9, 7, 2, 138, 3, 33, 126, 7, 41, 39, 0, 0, 198, 199, 149,
                                          100
                                          , 2, 1, 0, 5, 10
                                      },
                                      {
                                          626, 11, 3, 5, 1232, 12, 5, 4, 207, 2, 26, 230, 125, 204, 132, 1, 0, 596, 113,
                                          596, 107, 5, 67, 0, 4, 12
                                      },
                                      {
                                          107, 50, 1029, 149, 2067, 53, 471, 157, 3, 2, 151, 370, 292, 2100, 220, 18, 3,
                                          250, 1038, 1008, 25, 65, 2, 4, 0, 42
                                      },
                                      {
                                          171, 0, 0, 0, 125, 0, 0, 0, 0, 0, 0, 0, 0, 1, 12, 0, 0, 0, 0, 1, 28, 0, 0, 0,
                                          0,
                                          0
                                      },
                                      {
                                          286, 4, 2, 0, 297, 11, 13, 7, 53, 0, 4, 118, 1, 11, 247, 4, 0, 113, 32, 218,
                                          116,
                                          1, 4, 0, 1, 3
                                      },
                                      {
                                          473, 80, 23, 99, 802, 49, 64, 13, 787, 2, 33, 639, 27, 43, 126, 11, 0, 9, 239,
                                          332, 186, 12, 1, 0, 28, 21
                                      },
                                      {
                                          378, 41, 3, 2, 567, 9, 5, 5, 581, 0, 5, 23, 244, 4, 101, 80, 0, 1, 44, 86, 101
                                          , 0
                                          , 6, 0, 0, 0
                                      },
                                      {
                                          407, 56, 36, 1458, 1176, 112, 1045, 69, 534, 9, 171, 59, 57, 394, 184, 13, 0,
                                          21,
                                          496, 701, 194, 24, 36, 1, 5, 159
                                      },
                                      {
                                          16, 68, 196, 111, 6, 60, 56, 119, 7, 7, 35, 344, 193, 769, 13, 73, 0, 590, 157
                                          ,
                                          114, 26, 17, 48, 3, 7, 122
                                      },
                                      {
                                          188, 0, 0, 5, 111, 43, 0, 25, 107, 0, 2, 75, 2, 1, 146, 56, 0, 391, 13, 42, 44
                                          , 0
                                          , 0, 0, 0, 0
                                      },
                                      {0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 16, 0, 0, 0, 0, 0},
                                      {
                                          539, 180, 75, 426, 1251, 119, 211, 129, 548, 12, 212, 190, 122, 229, 367, 41,
                                          0,
                                          89, 443, 601, 314, 20, 77, 2, 3, 94
                                      },
                                      {
                                          272, 84, 1132, 18, 941, 46, 77, 51, 664, 10, 72, 47, 50, 9, 372, 278, 0, 62,
                                          359,
                                          1432, 92, 42, 46, 0, 19, 18
                                      },
                                      {
                                          381, 36, 5, 6, 2158, 29, 38, 85, 595, 3, 20, 160, 21, 24, 139, 5, 1, 302, 419,
                                          335, 197, 8, 98, 0, 8, 248
                                      },
                                      {
                                          35, 64, 213, 35, 144, 386, 94, 26, 10, 1, 38, 62, 270, 1624, 1, 56, 0, 426,
                                          463,
                                          284, 2, 13, 9, 4, 0, 12
                                      },
                                      {
                                          22, 1, 0, 1, 523, 0, 0, 0, 97, 0, 0, 0, 0, 0, 525, 1, 0, 1, 0, 2, 1, 0, 4, 0,
                                          0,
                                          0
                                      },
                                      {
                                          298, 1, 0, 1, 591, 0, 0, 2, 480, 14, 0, 1, 1, 5, 153, 0, 1, 0, 4, 0, 67, 0, 0,
                                          0,
                                          0, 0
                                      },
                                      {5, 0, 1, 0, 6, 0, 0, 0, 15, 0, 1, 0, 0, 0, 2, 14, 0, 0, 0, 7, 3, 0, 0, 0, 1, 1},
                                      {0, 1, 1, 2, 10, 0, 1, 1, 1, 0, 4, 0, 30, 8, 3, 9, 0, 3, 13, 1, 0, 0, 1, 1, 0, 0},
                                      {
                                          37, 1, 1, 2, 400, 6, 10, 2, 177, 1, 5, 15, 3, 8, 19, 6, 0, 1, 7, 78, 529, 4,
                                          101,
                                          0, 1, 2
                                      }
                                  };


        //19, najlepsze nasze kolo 21000000
        private static int[,] A = {
                                      {
                                          0, 12, 36, 28, 52, 44, 110, 126, 94, 63, 130, 102, 65, 98, 132, 132, 126, 120,
                                          126
                                      },
                                      {12, 0, 24, 75, 82, 75, 108, 70, 124, 86, 93, 106, 58, 124, 161, 161, 70, 64, 70},
                                      {36, 24, 0, 47, 71, 47, 110, 73, 126, 71, 95, 110, 46, 127, 163, 163, 73, 67, 73},
                                      {
                                          28, 75, 47, 0, 42, 34, 148, 111, 160, 52, 94, 148, 49, 117, 104, 109, 111, 105
                                          ,
                                          111
                                      },
                                      {
                                          52, 82, 71, 42, 0, 42, 125, 136, 102, 22, 73, 125, 32, 94, 130, 130, 136, 130,
                                          136
                                      },
                                      {
                                          44, 75, 47, 34, 42, 0, 148, 111, 162, 52, 96, 148, 49, 117, 152, 152, 111, 105
                                          ,
                                          111
                                      },
                                      {
                                          110, 108, 110, 148, 125, 148, 0, 46, 46, 136, 47, 30, 108, 51, 79, 79, 46, 47,
                                          41
                                      },
                                      {
                                          126, 70, 73, 111, 136, 111, 46, 0, 69, 141, 63, 46, 119, 68, 121, 121, 27, 24,
                                          36
                                      },
                                      {94, 124, 126, 160, 102, 162, 46, 69, 0, 102, 34, 45, 84, 23, 80, 80, 69, 64, 51},
                                      {
                                          63, 86, 71, 52, 22, 52, 136, 141, 102, 0, 64, 118, 29, 95, 131, 131, 141, 135,
                                          141
                                      },
                                      {130, 93, 95, 94, 73, 96, 47, 63, 34, 64, 0, 47, 56, 54, 94, 94, 63, 46, 24},
                                      {
                                          102, 106, 110, 148, 125, 148, 30, 46, 45, 118, 47, 0, 100, 51, 89, 89, 46, 40,
                                          36
                                      },
                                      {
                                          65, 58, 46, 49, 32, 49, 108, 119, 84, 29, 56, 100, 0, 77, 113, 113, 119, 113,
                                          119
                                      },
                                      {98, 124, 127, 117, 94, 117, 51, 68, 23, 95, 54, 51, 77, 0, 79, 79, 68, 62, 51},
                                      {
                                          132, 161, 163, 104, 130, 152, 79, 121, 80, 131, 94, 89, 113, 79, 0, 10, 113,
                                          107,
                                          119
                                      },
                                      {
                                          132, 161, 163, 109, 130, 152, 79, 121, 80, 131, 94, 89, 113, 79, 10, 0, 113,
                                          107,
                                          119
                                      },
                                      {126, 70, 73, 111, 136, 111, 46, 27, 69, 141, 63, 46, 119, 68, 113, 113, 0, 6, 24}
                                      ,
                                      {120, 64, 67, 105, 130, 105, 47, 24, 64, 135, 46, 40, 113, 62, 107, 107, 6, 0, 12}
                                      ,
                                      {
                                          126, 70, 73, 111, 136, 111, 41, 36, 51, 141, 24, 36, 119, 51, 119, 119, 24, 12
                                          , 0
                                      }
                                  };

        private static int[,] B = {
                                      {
                                          0, 76687, 0, 415, 545, 819, 135, 1368, 819, 5630, 0, 3432, 9082, 1503, 0, 0,
                                          13732, 1368, 1783
                                      },
                                      {
                                          76687, 0, 40951, 4118, 5767, 2055, 1917, 2746, 1097, 5712, 0, 0, 0, 268, 0,
                                          1373,
                                          268, 0, 0
                                      },
                                      {
                                          0, 40951, 0, 3848, 2524, 3213, 2072, 4225, 566, 0, 0, 404, 9372, 0, 972, 0,
                                          13538
                                          , 1368, 0
                                      },
                                      {415, 4118, 3848, 0, 256, 0, 0, 0, 0, 829, 128, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {545, 5767, 2524, 256, 0, 0, 0, 0, 47, 1655, 287, 0, 42, 0, 0, 0, 226, 0, 0},
                                      {819, 2055, 3213, 0, 0, 0, 0, 0, 0, 926, 161, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {135, 1917, 2072, 0, 0, 0, 0, 0, 196, 1538, 196, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {1368, 2746, 4225, 0, 0, 0, 0, 0, 0, 0, 301, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {819, 1097, 566, 0, 47, 0, 196, 0, 0, 1954, 418, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {5630, 5712, 0, 829, 1655, 926, 1538, 0, 1954, 0, 0, 282, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 0, 128, 287, 161, 196, 301, 418, 0, 0, 1686, 0, 0, 0, 0, 226, 0, 0},
                                      {3432, 0, 404, 0, 0, 0, 0, 0, 0, 282, 1686, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {9082, 0, 9372, 0, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {1503, 268, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 972, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 99999, 0, 0, 0},
                                      {0, 1373, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 99999, 0, 0, 0, 0},
                                      {13732, 268, 13538, 0, 226, 0, 0, 0, 0, 0, 226, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {1368, 0, 1368, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {1783, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
                                  };

        private static int[,] X = { //16, 68
                                      {0, 2, 1, 1, 2, 1, 1, 2, 2, 3, 0, 0, 0, 0, 0, 0},
                                      {2, 0, 1, 1, 1, 0, 0, 1, 1, 2, 0, 0, 0, 0, 0, 0},
                                      {1, 1, 0, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0,},
                                      {1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0},
                                      {2, 1, 0, 0, 0, 1, 1, 1, 1, 2, 0, 0, 0, 0, 0, 0},
                                      {1, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0},
                                      {1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0},
                                      {2, 1, 1, 1, 1, 1, 1, 0, 2, 2, 0, 0, 0, 0, 0, 0},
                                      {2, 1, 1, 1, 1, 1, 1, 2, 0, 2, 0, 0, 0, 0, 0, 0},
                                      {3, 2, 1, 1, 2, 1, 1, 2, 2, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
                                      {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
                                  };

        private static int[,] Y = {
                                      {0, 0, 0, 1, 0, 1, 1, 2, 0, 1, 1, 2, 1, 2, 2, 3},
                                      {0, 0, 1, 0, 1, 0, 2, 1, 1, 0, 2, 1, 2, 1, 3, 2},
                                      {0, 1, 0, 0, 1, 2, 0, 1, 1, 2, 0, 1, 2, 3, 1, 2},
                                      {1, 0, 0, 0, 2, 1, 1, 0, 2, 1, 1, 0, 3, 2, 2, 1},
                                      {0, 1, 1, 2, 0, 0, 0, 1, 1, 2, 2, 3, 0, 1, 1, 2},
                                      {1, 0, 2, 1, 0, 0, 1, 0, 2, 1, 3, 2, 1, 0, 2, 1},
                                      {1, 2, 0, 1, 0, 1, 0, 0, 2, 3, 1, 2, 1, 2, 0, 1},
                                      {2, 1, 1, 0, 1, 0, 0, 0, 3, 2, 2, 1, 2, 1, 1, 0},
                                      {0, 1, 1, 2, 1, 2, 2, 3, 0, 0, 0, 1, 0, 1, 1, 2},
                                      {1, 0, 2, 1, 2, 1, 3, 2, 0, 0, 1, 0, 1, 0, 2, 1},
                                      {1, 2, 0, 1, 2, 3, 1, 2, 0, 1, 0, 0, 1, 2, 0, 1},
                                      {2, 1, 1, 0, 3, 2, 2, 1, 1, 0, 0, 0, 2, 1, 1, 0},
                                      {1, 2, 2, 3, 0, 1, 1, 2, 0, 1, 1, 2, 0, 0, 0, 1},
                                      {2, 1, 3, 2, 1, 0, 2, 1, 1, 0, 2, 1, 0, 0, 1, 0},
                                      {2, 3, 1, 2, 1, 2, 0, 1, 1, 2, 0, 1, 0, 1, 0, 0},
                                      {3, 2, 2, 1, 2, 1, 1, 0, 2, 1, 1, 0, 1, 0, 0, 0}
                                  };
    }
}